import { getSeed } from ".."
import { BelongsTo, Column, HasOne, Seed } from "../types"
import { get } from "@/utils/request"

const defaultActionName = 'lookup'

/**
 * micro.seed.action 在服务【micro】下去找
 * ~.seed.action或.seed.action 在应用下去找
 * seed.action 在当前所在的服务下去找
 * action 在当前seed下去找
 * 
 * 引用类型的rel格式为：micro.seed.action
 */
export function getRelAction(column: Column) {
  if(column.type !== 'ref') return void 0

  const { micro, seed } = column
  let rel = column.rel || getInferRel(column)
  if(!rel) throw Error(`请为【${seed.name}】模块下的【${column.name}】列配置【rel】`)

  console.log('rel=====', rel)
  const items = rel.split('.')
  const len = items.length
  if(len == 1) {
    const [actionName] = items
    const action = seed.actions?.[actionName]
    if(!action) throw Error(`【${seed.name}】模块下的功能【${actionName}】不存在`)

    return action
  }

  if(len == 2) {
    const [seedName, actionName] = items
    const seed = getSeed(seedName, micro?.name)
    const action = seed.actions?.[actionName]
    if(!action) throw Error(`【${seed.name}】模块下的功能【${actionName}】不存在`)

    return action
  }

  if(len === 3) {
    const [microName, seedName, actionName] = items
    const seed = getSeed(seedName, '~' === microName ? void 0 : microName)
    const action = seed.actions?.[actionName]
    if(!action) throw Error(`【${seed.name}】模块下的功能【${actionName}】不存在`)

    return action
  }

  throw Error(`【${seed.name}】模块下的【${column.name}】列下的【rel】配置错误`)
}

/**
 * micro.seed.action 在服务【micro】下去找
 * .seed.action 在应用下去找
 * seed.action 在当前所在的服务下去找
 * action 在当前seed下去找
 * 
 * rel > belongsTo > has
 * rel: micro.seed.action.column
 * belongsTo: targetSeed.lookup.targetColumn > targetSeed.[type:page].targetColumn
 * has: selfSeed.lookup.selfColumn > selfSeed.[type:page].selfColumn
 */
// export function getRelAction(column: Column) {
//   const rel = column.rel
//   if(rel) {
//     const pos = rel.lastIndexOf('.')
//     const relActionName = rel.substring(0, pos)
//     const columnName = rel.substring(pos)
//     const items = relActionName.split('.')
//     const len = items.length

//     const { micro, seed } = column
//     if(len == 1) {
//       const action = seed.actions?.[relActionName]
//       if(!action) throw Error(`【${seed.name}】模块下的功能【${relActionName}】不存在`)

//       return {action, columnName }
//     }

//     if(len == 2) {
//       const [seedName, actionName] = items
//       const seed = getSeed(seedName, micro?.name)
//       const action = seed.actions?.[actionName]
//       if(!action) throw Error(`【${seed.name}】模块下的功能【${actionName}】不存在`)

//       return {action, columnName}
//     }

//     if(len === 3) {
//       const [microName, seedName, actionName] = items
//       const seed = getSeed(seedName, microName)
//       const action = seed.actions?.[actionName]
//       if(!action) throw Error(`【${seed.name}】模块下的功能【${actionName}】不存在`)

//       return {action, columnName}
//     }

//     throw Error(`【${seed.name}】模块下的【${column.name}】列下的【rel】配置错误`)
//   }

//   const belongsTo = column.seed.belongsTo
//   if(belongsTo) {
//     const r = getBelongsToRelation(belongsTo, column)
//     if(r) {
//       const columnName = r.targetColumn
//       const relSeed = getSeed(r.seedName, column.micro.name)
//       let action = relSeed.actions[defaultActionName]
//       if(action) return {action, columnName}
      
//       for(const actionName in relSeed.actions) {
//         const action = relSeed.actions[actionName]
//         if(action.type === 'page') return {action, columnName}
//       }

//       throw Error(`【${r.seedName}】模块下的功能【${defaultActionName}】不存在`)
//     }
//   }

//   const app = column.app
//   if(app.seeds) {
//     const action = getHasRefAction(app.seeds, column)
//     if(action) return action
//   }

//   const micros = app.micros
//   if(micros) {
//     for(const microName in micros) {
//       const micro = micros[microName]
//       if(micro.seeds) {
//         const relAction = getHasRefAction(micro.seeds, column)
//         if(relAction) return relAction
//       }
//     }
//   }

//   return {}
// }

function getInferRel(column: Column) {
  const belongsTo = column.seed.belongsTo
  if(belongsTo) {
    for(const cross in belongsTo) {
      const relation = belongsTo[cross]
      if(relation.selfColumn === column.name) {
        return `${relation.seedName}.${defaultActionName}`
      }
    }
  }

  const seeds = (column.micro || column.app).seeds // 当前服务
  for(const seedName in seeds) {
    const seed = seeds[seedName]
    const hasOne = seed.hasOne
    if(hasOne) {
      for(const cross in hasOne) {
        const relation = hasOne[cross]
        if(relation.seedName === column.seed.name && relation.targetColumn === column.name) {
          return `${relation.selfSeed.name}.${defaultActionName}`
        }
      }
    }

    const hasMany = seed.hasMany
    if(hasMany) {
      for(const cross in hasMany) {
        const relation = hasMany[cross]
        if(relation.seedName === column.seed.name && relation.targetColumn === column.name) {
          return `${relation.selfSeed.name}.${defaultActionName}`
        }
      }
    }
  }

  return void 0
}

export function getRelUrl(column: Column) {
  const { micro, seed } = column
  if(!column.rel) return (micro ? `${micro.name}/` : '') + `${seed.name}/${defaultActionName}`

  const pos = column.rel.lastIndexOf('.')
  const rel = column.rel.substring(0, pos)
  const items = rel.split('.')
  const len = items.length
  if(len == 1) return (micro ? `${micro.name}/` : '') + `${seed.name}/${rel}`
  if(len == 2) return (micro ? `${micro.name}/` : '') + `${items[0]}/${items[1]}`
  
  const [microName, seedName, actionName] = items
  if(microName) return `${microName}/${seedName}/${actionName}`

  return `${seedName}/${actionName}`
}

function getHasRefAction(seeds: Record<string, Seed>, column: Column) {
  for(const seedName in seeds) {
    const seed = seeds[seedName]
    const hasOne = seed.hasOne
    if(hasOne) {
      const action = getHasOneRefAction(seed, hasOne, column)
      if(action) return action
    }

    const hasMany = seed.hasMany
    if(hasMany) {
      const refAction = getHasOneRefAction(seed, hasMany, column)
      if(refAction) return refAction
    }
  }

  return {}
}

function getHasOneRefAction(seed: Seed, hasOne: Record<string, HasOne>, column: Column) {
  const r = getHasOneRelation(hasOne, column)
  if(r) {
    const columnName = r.selfColumn
    let action = seed.actions[defaultActionName]
    if(action) return {action, columnName}
    
    for(const actionName in seed.actions) {
      const action = seed.actions[actionName]
      if(action.type === 'page') return {action, columnName}
    }

    throw Error(`【${seed.name}】模块下的功能【${defaultActionName}】不存在`)
  }

  return {}
}

function getBelongsToRelation(belongsTo: Record<string, BelongsTo>, column: Column) {
  for(const cross in belongsTo) {
    const relation = belongsTo[cross]
    if(relation.selfColumn === column.name) return relation
  }

  return void 0
}

function getHasOneRelation(hasOne: Record<string, HasOne>, column: Column) {
  for(const cross in hasOne) {
    const relation = hasOne[cross]
    if(relation.seedName === column.seed.name && relation.targetColumn === column.name) return relation
  }

  return void 0
}

export async function labelApi(column: Column, id: string) {
  const { rel, seed, micro } = column // 引用类型的rel值格式为: micro.seed.action
  const items = rel.split('.')
  const len = items.length

  if(!id) return '<空>'

  let url
  if(len === 1) { // action
    url = `${micro ? micro.name + '/' : ''}${seed.name}/label/${id}`
  } else if(len === 2) { // seed.action
    const [seedName] = items
    url = `${micro ? micro.name + '/' : ''}${seedName}/label/${id}`
  } else { // micro.seed.action
    const [microName, seedName] = items
    url = `${microName}/${seedName}/label/${id}`
  }

  return await get(url)
}